package io.cloud.tec.project.util;

import org.apache.hc.client5.http.classic.methods.*;
import org.apache.hc.client5.http.config.RequestConfig;
import org.apache.hc.client5.http.impl.classic.CloseableHttpClient;
import org.apache.hc.client5.http.impl.classic.HttpClients;
import org.apache.hc.core5.http.io.entity.EntityUtils;
import org.apache.hc.core5.http.io.entity.StringEntity;
import org.apache.hc.core5.util.Timeout;

import java.io.IOException;
import java.nio.charset.StandardCharsets;

public class HttpApiUtils {
    private static final int DEFAULT_TIMEOUT = 30000;
    private static final int DEFAULT_RETRY_TIMES = 3;
    private static final int DEFAULT_RETRY_INTERVAL = 1000;

    static RequestConfig config = RequestConfig.custom()
            .setConnectTimeout(Timeout.ofMilliseconds(DEFAULT_TIMEOUT))
            .setConnectionRequestTimeout(Timeout.ofMilliseconds(DEFAULT_TIMEOUT))
            .setResponseTimeout(Timeout.ofMilliseconds(DEFAULT_TIMEOUT))
            .build();
    static CloseableHttpClient httpClient = HttpClients.custom().setDefaultRequestConfig(config).build();

    public static String sendHttpRequest(String url, String method, String contentType, String requestBody) throws Exception {

        return sendHttpRequest(url, method, contentType, requestBody, DEFAULT_RETRY_TIMES, DEFAULT_RETRY_INTERVAL);
    }

    public static String sendHttpRequest(String url, String method, String contentType, String requestBody, int retryTimes, int retryInterval) throws Exception {
        int retryCount = 0;
        while (retryCount < retryTimes) {
            try {
                HttpUriRequest httpRequest;
                switch (method.toUpperCase()) {
                    case "GET":
                        httpRequest = new HttpGet(url);
                        break;
                    case "POST":
                        httpRequest = new HttpPost(url);
                        break;
                    case "PUT":
                        httpRequest = new HttpPut(url);
                        break;
                    case "DELETE":
                        httpRequest = new HttpDelete(url);
                        break;
                    default:
                        throw new IllegalArgumentException("Invalid Http request method: " + method);
                }
                httpRequest.setHeader("Content-Type", contentType);
                httpRequest.setEntity(new StringEntity(requestBody, StandardCharsets.UTF_8));
                return EntityUtils.toString(httpClient.execute(httpRequest).getEntity());
            } catch (IOException e) {
                retryCount++;
                if (retryCount >= retryTimes) {
                    throw new Exception("Http request failed after " + retryCount + " retries.", e);
                }
                Thread.sleep(retryInterval);
            }
        }
        throw new Exception("Http request failed after");
    }
}
